package com.next

import grails.transaction.Transactional
import org.springframework.security.access.annotation.Secured

import static org.springframework.http.HttpStatus.*

@Secured(['ROLE_ADMINISTRATOR', 'ROLE_COMPANY_ADMINISTRATOR', 'ROLE_COMPANY_USER'])
@Transactional(readOnly = true)
class ContactController
{

    static allowedMethods = [save: "POST", update: "PUT", delete: "DELETE", appRegister: "POST", appLogin: "POST"]

    def springSecurityService
    def exportService

    def index(Integer max)
    {
        def username = springSecurityService?.getPrincipal()?.username
        def contactList = Contact.findAll("from Contact where user.username = '${username}' order by modifiedDate desc", [max: params.max ?: 10, offset: params.offset ?: 0])
        def count = Contact.executeQuery("select count(id) from Contact where user.username = '${username}'")

        respond contactList, model: [contactCount: count[0]]

    }

    def show(Contact contact)
    {
        def addressList = Address.findAll("from Address where contact.id = ?", [contact.id])
        def noteList = Note.findAll("from Note where contact.id = ?", [contact.id])
        def attachmentList = Attachment.findAll("from Attachment where contact.id = ?", [contact.id])
        def teamList = ContactTeam.findAll("from ContactTeam where contact.id = ?", [contact.id])
        def flexFieldInstanceList = FlexFieldInstance.findAll("from FlexFieldInstance where contact.id = ?", [contact.id])
        def appointmentList = Activity.findAll("from Activity where contact.id = ? and type.id = ?", [contact.id, ActivityType.find("from ActivityType where name = 'Appointment'")?.id])
        def taskList = Activity.findAll("from Activity where contact.id = ? and type.id = ?", [contact.id, ActivityType.find("from ActivityType where name = 'Task'")?.id])
        respond contact, model: [addressList: addressList, noteList: noteList, attachmentList: attachmentList, teamList: teamList, flexFieldInstanceList: flexFieldInstanceList, appointmentList: appointmentList, taskList: taskList, teamName: 'contactTeam']
    }

    def create()
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)

        Company company = Company.findAll()[0]
        Boolean enableTerritory = company.enableContactTerritory
        if (company.enableAccountTerritory && company.inheritanceAccountTerritory)
        {
            enableTerritory = false
        }
        respond new Contact(params), model: [enableTerritory: enableTerritory, user: user]
    }

    @Transactional
    def save(Contact contact)
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)

        if (contact == null)
        {
            transactionStatus.setRollbackOnly()
            notFound()
            return
        }

        if (contact.hasErrors())
        {
            transactionStatus.setRollbackOnly()
            respond contact.errors, model: [user: user], view: 'create'
            return
        }

        contact.save flush: true

        request.withFormat {
            form multipartForm {
                flash.message = message(code: 'default.created.message', args: [message(code: 'contact.label',
                                                                                        default: 'Contact'), contact
                    .id])
                redirect contact
                // redirect action: "create"
            }
            '*' { respond contact, [status: CREATED] }
        }
    }

    @Transactional
    def saveAndCreate(Contact contact)
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)

        if (contact == null)
        {
            transactionStatus.setRollbackOnly()
            notFound()
            return
        }

        if (contact.hasErrors())
        {
            transactionStatus.setRollbackOnly()
            respond contact.errors, model: [user: user], view: 'create'
            return
        }

        contact.save flush: true

        request.withFormat {
            form multipartForm {
                flash.message = message(code: 'default.created.message', args: [message(code: 'contact.label',
                                                                                        default: 'Contact'), contact
                    .id])
                // redirect contact
                redirect action: "create"
            }
            '*' { respond contact, [status: CREATED] }
        }
    }

    def edit(Contact contact)
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)
        respond contact, model: [user: user]
    }

    @Transactional
    def update(Contact contact)
    {
        def username = springSecurityService?.getPrincipal()?.username
        def user = User.findByUsername(username)

        if (contact == null)
        {
            transactionStatus.setRollbackOnly()
            notFound()
            return
        }

        if (contact.hasErrors())
        {
            transactionStatus.setRollbackOnly()
            respond contact.errors, model: [user: user], view: 'edit'
            return
        }

        contact.save flush: true


        request.withFormat {
            form multipartForm {
                flash.message = message(code: 'default.updated.message', args: [message(code: 'contact.label',
                                                                                        default: 'Contact'), contact
                    .id])
                redirect contact
            }
            '*' { respond contact, [status: OK] }
        }

    }

    @Transactional
    def delete(Contact contact)
    {
        if (contact == null)
        {
            transactionStatus.setRollbackOnly()
            notFound()
            return
        }

        contact.delete flush: true

        request.withFormat {
            form multipartForm {
                flash.message = message(code: 'default.deleted.message', args: [message(code: 'contact.label',
                                                                                        default: 'Contact'), contact
                    .id])
                redirect action: "index", method: "GET"
            }
            '*' { render status: NO_CONTENT }
        }
    }

    protected void notFound()
    {
        request.withFormat {
            form multipartForm {
                flash.message = message(code: 'default.not.found.message', args: [message(code: 'contact.label',
                                                                                          default: 'Contact'), params
                    .id])
                redirect action: "index", method: "GET"
            }
            '*' { render status: NOT_FOUND }
        }
    }

    def searchContact()
    {
        def username = springSecurityService?.getPrincipal()?.username
        def fullName = params["fullName"]
        String sql = "from Contact as u where 1=1 and u.user.username = '${username}'"
        if (fullName)
        {
            sql += " and u.fullName like '%${fullName}%'"
        }
        String countSql = "select count(u.id) " + sql
        sql += ' order by modifiedDate desc'

        def list = Contact.findAll(sql, [max: params.max ?: 10, offset: params.offset ?: 0])
        def count = Contact.executeQuery(countSql)

        respond list, model: [contactCount: count[0], params: params], view: 'index'
    }

    def exportContact()
    {
        def username = springSecurityService?.getPrincipal()?.username
        def fullName = params["fullName"]
        String sql = "from Contact as u where 1=1 and u.user.username = '${username}'"
        if (fullName)
        {
            sql += " and u.fullName like '%${fullName}%'"
        }
        String countSql = "select count(u.id) " + sql
        sql += ' order by modifiedDate desc'

        def list = Contact.findAll(sql)
        def count = Contact.executeQuery(countSql)

        if (params?.f && params.f != "html")
        {
            response.contentType = grailsApplication.config.grails.mime.types[params.f]
            response.setHeader("Content-disposition", "attachment; filename=contact.${params.extension}")
            List fields = ["fullName", "user.fullName", "salutation.name", "title", "job", "email", "fax", "phone", "cellphone", "wechat", "qq", "birthday", "hometown", "hobby", "taboo", "country.name", "city.name", "idNumber", "maritalStatus", "gender", "source.name", "cellphoneHasVerified", "active", "account.name", "lead.fullName", "type.name", "level.name", "hireDate", "leaveDate", "createdDate", "modifiedDate"]
            Map labels = ["fullName": "姓名", "user.fullName": "所有者", "salutation.name": "称谓", "title": "头衔", "job": "职务", "email": "邮箱", "fax": "传真", "phone": "座机", , "cellphone": "手机", "wechat": "微信", "qq": "QQ", "birthday": "生日", "hometown": "家乡", "hobby": "爱好", "taboo": "禁忌", "country.name": "国籍", "city.name": "城市", "idNumber": "身份证号", "maritalStatus": "婚姻状况", "gender": "性别", "source.name": "联系人来源", "cellphoneHasVerified": "手机已验证", "active": "是否激活", "account.name": "客户", "lead.fullName": "线索", "type.name": "联系人类型", "level.name": "联系人分级", "hireDate": "入职时间", "leaveDate": "离职时间", "createdDate": "创建时间", "modifiedDate": "修改时间"]
            exportService.export(params.f, response.outputStream, list, fields, labels, [:], [:])
        }
    }
}
